进程管理-经典同步问题

生产者消费者问题

  1. 问题描述
    生产者进程和消费者进程共享一个缓冲区,只有缓冲区未满时,生产者进程才可以吧消息放入缓冲区,只有当缓冲区非空时,消费者进程才可以从中取消息,缓冲区为临界资源
  2. 思路
    解决互斥和同步PV操作问题
  3. 代码
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    semaphore mutex=1;
    semaphore full=0;
    semaphore empty=n;
    producer(){
    while1){
    生产数据;
    P(empty);
    P(mutex);
    数据放入缓冲区;
    V(mutex);
    V(full);
    }
    }
    comsumer(){
    while1){
    P(full);
    P(mutex);
    从缓冲区中取出数据;
    V(mutex);
    V(empty);
    消费数据;
    }
    }

读者-写者问题

  1. 问题描述
    有读者进程和写者进程,关系如下:
    • 多个读者可同时对文件进行读操作
    • 只允许一个写者往文件写数据
    • 写者完成工作之前,不允许其他读者或写者操作
    • 写者执行操作之间,应让已有读者和写者全部退出
  2. 思路
    写者和写者、读者都互斥;读者与写者互斥,读者间同步
    利用count记录读者数目,mutex用于count的互斥访问,rx用于读写者的互斥访问
  3. 代码
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    int count =0;
    semaphore mutex=1;
    semaphore re=1;
    writer(){
    while(1){
    P(rw);
    写入数据;
    V(rw);
    }
    }
    reader(){
    while(1){
    P(mutex);
    if(count == 0)
    P(rw);
    count++;
    V(mutex);
    读;
    P(mutex);
    count--;
    if(count == 0)
    V(rw);
    V(mutex);
    }
    }

哲学家进餐问题

  1. 问题描述
    一张圆桌上坐在五个哲学家,每个哲学家左右两边各有一只筷子,哲学家一次只能拿一只筷子,拿到两只筷子才可以进餐,否则等待,进餐后放下筷子,继续思考。
  2. 思路
    定义互斥型号量数组chopstick[5]={1,1,1,1,1},用于对筷子的互斥访问,哲学家编号0—4,哲学家i左边的筷子为编号i;右边的筷子为编号(i+1)%5;mutex表示对筷子的互信号量

  3. 代码

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    semaphore chopstick[5]={1,1,1,1,1}
    Pi(){
    do{
    p(mutex);
    P(chopstick[i]);
    P(chopstick[(i+1)%5]);
    V(mutex);
    eat;
    V(chopstick[i]);
    V(chopstick[(i+1)%5]);
    think;
    }while(1);
    }

吸烟者问题